package com.android.adpater;

import android.content.Context;
import android.util.SparseArray;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AdapterView;

import androidx.annotation.ColorInt;
import androidx.annotation.ColorRes;
import androidx.annotation.NonNull;
import androidx.annotation.StringRes;
import androidx.viewpager.widget.PagerAdapter;

import com.android.adpater.interfaces.IAdapter;
import com.android.adpater.interfaces.IData;
import com.android.adpater.interfaces.OnClickListItemListener;

import java.util.ArrayList;
import java.util.List;

/**
 *
 * @author GYL
 * @version 1.0
 * PagerAdapter 基类
 */
public abstract class BasePagerAdapter<T> extends PagerAdapter implements IData<T>, IAdapter<T> {

  private static final int IGNORE_ITEM_VIEW_TYPE = AdapterView.ITEM_VIEW_TYPE_IGNORE;
  private final List<T> mData;
  //protected RecycleCacheViewPager recycleBin;
  //private boolean isRecycleView = false;
  private SparseArray<View> mViewSparseArray;
  private int mChildCount = 0;
  private OnClickListItemListener onPageViewClick;
  //
  protected Context mContext;
  protected LayoutInflater mInflater;

  private boolean enableNotifyDataSetChanged = true;

  /**
   * @Description Constructor
   */
  public BasePagerAdapter(Context context) {
    this(context, null);
  }

  public BasePagerAdapter(Context context, ArrayList<T> list) {
    this.mContext = context;
    this.mInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    this.mData = list == null ? new ArrayList<T>() : new ArrayList<T>(list);
    this.mViewSparseArray = new SparseArray<>();
  }

  @Override
  public String getString(@StringRes int strId, Object ... obj){
    if(obj==null){
      return mContext.getString(strId);
    }else{
      return mContext.getString(strId, obj);
    }
  }

  @Override
  public @ColorInt
  int getColor(@ColorRes int colorId){
    return AdapterViewHelper.getColor(mContext,colorId);
  }

  @Override
  public void notifyDataSetChanged() {
    this.mChildCount = getCount();
    if (enableNotifyDataSetChanged) {
      super.notifyDataSetChanged();
    }
  }

  @Override
  public void enableNotifyDataSetChanged(boolean enable) {
    this.enableNotifyDataSetChanged = enable;
  }

  @Override
  public final Object instantiateItem(ViewGroup container, int position) {
    //
    T item = getPagerItem(position);
    final AdapterViewHelper baseAdapter = AdapterViewHelper
        .get(mContext, mViewSparseArray.get(position), container,
            getLayoutResId(getItemViewType(position)), position);
    onBindView(baseAdapter, item, position);
    baseAdapter.setAssociatedObject(item);
    //
    View view = baseAdapter.getView();
    mViewSparseArray.put(position, view);
    container.addView(view, 0);
    return view;
  }

  @Override
  public final void destroyItem(ViewGroup container, int position, Object object) {
    container.removeView((View) object);
    int viewType = getItemViewType(position);
    if (viewType != IGNORE_ITEM_VIEW_TYPE) {
      mViewSparseArray.remove(position);
    }
  }

  @Override
  public final boolean isViewFromObject(View view, Object object) {
    return view == object;
  }


  public int getViewTypeCount() {
    return 1;
  }

  /**
   * @see #IGNORE_ITEM_VIEW_TYPE
   */
  public int getItemViewType(int position) {
    return getItemViewType(getPagerItem(position), position);
  }

  @Override
  public int getItemViewType(T item, int position) {
    return 0;
  }

  @Override
  public List<T> getData() {
    return mData;
  }

  @Override
  public void setData(@NonNull List<T> list) {
    mData.clear();
    mData.addAll(list);
    notifyDataSetChanged();
  }

  @Override
  public void add(@NonNull T item) {
    mData.add(item);
    notifyDataSetChanged();
  }

  @Override
  public void insert(int position, @NonNull T item) {
    mData.add(position, item);
    notifyDataSetChanged();
  }

  @Override
  public void addAll(@NonNull List<T> list) {
    mData.addAll(list);
    notifyDataSetChanged();
  }

  @Override
  public void set(@NonNull T oldItem, @NonNull T newItem) {
    set(mData.indexOf(oldItem), newItem);
  }

  @Override
  public void set(int index, @NonNull T item) {
    if (index >= 0 && index < getCount()) {
      mData.set(index, item);
      notifyDataSetChanged();
    }
  }

  @Override
  public void remove(@NonNull T item) {
    mData.remove(item);
    notifyDataSetChanged();
  }

  @Override
  public void remove(int index) {
    if (index >= 0 && index < getCount()) {
      mData.remove(index);
      notifyDataSetChanged();
    }
  }

  @Override
  public void replaceAll(@NonNull List<T> item) {
    mData.clear();
    mData.addAll(item);
    notifyDataSetChanged();
  }

  @Override
  public boolean contains(@NonNull T item) {
    return mData.contains(item);
  }

  @Override
  public void clear() {
    mData.clear();
    notifyDataSetChanged();
  }

  @Override
  public void addArray(@NonNull T[] datas) {
    for (T data : datas) {
      mData.add(data);
    }
    notifyDataSetChanged();
  }

  @Override
  public int getCount() {
    return mData == null ? 0 : mData.size();
  }

  public T getPagerItem(int position) {
    return mData == null || mData.size() == 0 ? null : mData.get(position);
  }

  @Override
  public T getItem(int position) {
    return getPagerItem(position);
  }

  @Override
  public int getItemPosition(Object object) {
    // return POSITION_NONE;
    if (mChildCount > 0) {
      return POSITION_NONE;
    }
    return super.getItemPosition(object);
  }

  public void onDestroy() {
    if (mData != null) {
      mData.clear();
    }
    mViewSparseArray.clear();
  }

  /**
   * @return void
   * @Description View Item Onclick
   */
  @Override
  public void setOnListItemClick(OnClickListItemListener onPageViewItemClick) {
    this.onPageViewClick = onPageViewItemClick;
  }

  @Override
  public void addItemClick(View view, final Object obj, final int position) {
    view.setOnClickListener(new View.OnClickListener() {
      @Override
      public void onClick(View v) {
        if (onPageViewClick != null) {
          onPageViewClick.onPageViewItemClick(v, obj, position);
        }
      }
    });
  }

}